<script lang="ts" setup>
  import { ref, onMounted, onUnmounted, watch } from 'vue';
  import * as echarts from 'echarts/core';

  const props = defineProps({
    data: { type: Array as () => number[][], required: true },
    xAxisData: { type: Array as () => any[], required: true },
    yAxisData: { type: Array as () => string[], required: true },
    title: { type: String, default: '' },
    min: { type: Number, default: -25 },
    max: { type: Number, default: 25 },
  });

  const chartRef = ref<HTMLElement | null>(null);
  let chartInstance: echarts.ECharts | null = null;

  const option = ref<any>({
    title: {
      text: props.title,
      left: 'center',
      textStyle: {
        color: '#333',
        fontSize: 14,
      },
    },
    tooltip: {
      position: 'top',
      formatter: function (params: any) {
        return `${params.data[1]}: ${params.data[2].toFixed(2)}`;
      },
    },
    grid: {
      height: '70%',
      top: '15%',
      left: '8%',
      right: '8%',
      bottom: '3%',
    },
    xAxis: {
      type: 'category',
      data: props.xAxisData,
      splitLine: { show: false },
      axisLine: { lineStyle: { color: '#666' } },
      axisTick: { show: false },
      axisLabel: { color: '#333' },
    },
    yAxis: {
      type: 'category',
      data: props.yAxisData,
      splitLine: { show: false },
      axisLine: { lineStyle: { color: '#666' } },
      axisTick: { show: false },
      axisLabel: { color: '#333' },
    },
    visualMap: {
      min: props.min,
      max: props.max,
      calculable: true,
      orient: 'vertical',
      left: 'right',
      top: 'center',
      textStyle: { color: '#333' },
      inRange: {
        color: ['#313695', '#4575b4', '#74add1', '#abd9e9', '#e0f3f8', '#ffffcc', '#fee090', '#fdae61', '#f46d43', '#d73027', '#a50026'],
      },
    },
    series: [
      {
        name: '板形数据',
        type: 'heatmap',
        data: [],
        label: {
          show: false,
        },
        emphasis: {
          itemStyle: {
            shadowBlur: 10,
            shadowColor: 'rgba(0, 0, 0, 0.5)',
          },
        },
      },
    ],
  });

  const initCharts = () => {
    try {
      // 转换数据格式为热力图需要的格式
      const heatmapData: any[] = [];
      props.data.forEach((row, yIndex) => {
        row.forEach((value, xIndex) => {
          heatmapData.push([xIndex, yIndex, value]);
        });
      });

      option.value.series[0].data = heatmapData;
      option.value.xAxis.data = props.xAxisData;
      option.value.yAxis.data = props.yAxisData;
      option.value.title.text = props.title;
      option.value.visualMap.min = props.min;
      option.value.visualMap.max = props.max;

      if (chartRef.value && !chartInstance) {
        chartInstance = echarts.init(chartRef.value);
        chartInstance?.setOption(option.value, true);
      }
    } catch (error) {
      console.error('热力图初始化失败:', error);
    }
  };

  const updateChart = () => {
    const heatmapData: any[] = [];
    props.data.forEach((row, yIndex) => {
      row.forEach((value, xIndex) => {
        heatmapData.push([xIndex, yIndex, value]);
      });
    });

    option.value.series[0].data = heatmapData;
    option.value.xAxis.data = props.xAxisData;
    option.value.yAxis.data = props.yAxisData;
    option.value.title.text = props.title;
    option.value.visualMap.min = props.min;
    option.value.visualMap.max = props.max;

    chartInstance?.setOption(option.value, true);
    chartInstance?.resize();
  };

  onMounted(() => {
    setTimeout(() => {
      initCharts();
    }, 100);

    window.addEventListener('resize', () => chartInstance?.resize());
  });

  onUnmounted(() => {
    window.removeEventListener('resize', updateChart);
    chartInstance?.dispose();
  });

  watch(
    () => [props.data, props.xAxisData, props.yAxisData],
    () => updateChart(),
    { deep: true }
  );

  defineExpose({
    updateChart,
    chartRef,
  });
</script>

<template>
  <div ref="chartRef" class="chart-container"></div>
</template>

<style scoped>
  .chart-container {
    width: 100%;
    height: 100%;
  }
</style>
